import json
import urllib.parse as parse

import requests as req

import geetest_crack.utils.woff.woff_utils as woff_utils
from geetest_crack.my_geetest_validate import GeeValidate

common_headers = {
    'Referer': 'https://ss.cods.org.cn/',
    'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) '
                  'Chrome/79.0.3945.117 Safari/537.36'
}
proxies = {}

class CodsSpider:

    def __init__(self, keyword):
        self.keyword = keyword
        self.proxies = proxies
        self.invoke_json = {}
        self.gee_reg_str = str()
        self.searchToken = str()
        self.cookies = {}
        self.search_html = str()
        self.gee_validate = GeeValidate()

    def ajax_invoke(self):
        invoke_url = 'https://www.cods.org.cn/cods/ajax/invoke'
        zv_data = {
            'type': '1',
            'keywords': self.keyword
        }
        param_data = {
            '_ZVING_METHOD': 'search/query',
            '_ZVING_URL': '/',
            '_ZVING_DATA': json.dumps(zv_data),
            '_ZVING_DATA_FORMAT': 'json'
        }
        resp = self.__common_request_post(invoke_url, param_data)
        if 200 == resp.status_code:
            self.invoke_json = json.loads(resp.text)
            return True
        print('ajax/invoke其他状态码：', resp.status_code)
        return False

    def request_isearch(self):
        isearch_url = 'https://ss.cods.org.cn/isearch'
        param_data = {
            'jsonString': self.invoke_json['jsonString'],
            'sign': self.invoke_json['sign']
        }
        resp = self.__common_request_post(isearch_url, param_data)
        html = resp.text
        if html is not None and html.find('challenge') >= 0:
            reg_str = html[html.find('eval(') + len('eval('):html.find('initGeetest')]
            reg_str = reg_str[reg_str.find('{'):reg_str.find('}') + 1]
            searchToken = html[html.find('searchToken=') + len('searchToken='): html.find('"+gc')]
            cods_cookies = dict(resp.cookies)
            self.gee_reg_str = reg_str
            self.searchToken = searchToken
            self.cookies = cods_cookies
            return True
        return False

    def pass_geetest_validate(self):
        self.gee_validate.reset_reg_json_str(self.gee_reg_str)
        val_res = self.gee_validate.run()
        print('极验是否通过:', val_res)
        return val_res

    def searchR(self):
        encoded_kw = parse.quote(parse.quote(kw))
        gee_validate_arr = self.gee_validate.get_result()
        searchR_url = 'https://ss.cods.org.cn/latest/searchR?q=' + encoded_kw \
                      + '&t=common&currentPage=1&searchToken=' + self.searchToken \
                      + '&geetest_challenge=' + gee_validate_arr[0] \
                      + '&geetest_validate=' + gee_validate_arr[1] + '&geetest_seccode=' + gee_validate_arr[2]
        resp = req.get(url=searchR_url, headers=common_headers, cookies=self.cookies, proxies=self.proxies)
        search_html = resp.text
        if search_html.find('验证码安全认证已失效') >= 0:
            print('【查询结果】：验证码安全认证已失效')
            return False
        elif search_html.find('疑似代理IP将被永久封存') >= 0:
            print('【查询结果】：疑似代理IP将被永久封存')
            return False
        elif search_html.find('家符合条件的机构') >= 0:
            print('【查询结果】：已获取正常页面！')
            self.search_html = search_html
            return True
        elif search_html.find('当前系统访问量大') >= 0:
            print('【查询结果】：当前系统访问量大！')
            return False
        else:
            print('【查询结果】，其他情况：', search_html)
            return False

    def analyse_html_data(self):
        woff_utils.analyze_search_html(self.search_html)

    def run(self):
        return self.ajax_invoke() \
               and self.request_isearch() \
               and self.pass_geetest_validate() \
               and self.searchR() and self.analyse_html_data()

    def __common_request_get(self, url, params=None):
        return req.get(url=url, params=params, headers=common_headers, proxies=self.proxies)

    def __common_request_post(self, url, data):
        return req.post(url=url, data=data, headers=common_headers, proxies=self.proxies)


if __name__ == '__main__':
    kw = '南京'
    cods_spider = CodsSpider(kw)
    res = True
    while res:
        res = cods_spider.run() is False
